#pragma once

#include "xutil/macros/type.h"
#include "xutil/prefix.h"

/* *******************************************************
 *  macros
 */
// the state define
#define XU_STATE_DEFINE(type, state) (((type) << 16) | (state))

/* *******************************************************
 *  types
 */

// the state type enum
typedef enum __xu_state_type_e
{
    XU_STATE_TYPE_NONE     = 0,
    XU_STATE_TYPE_SOCK     = 1,
    XU_STATE_TYPE_HTTP     = 2,
    XU_STATE_TYPE_DATABASE = 3,
    XU_STATE_TYPE_SYSERROR = 4

} xu_state_type_e;

// the state enum
typedef enum __xu_state_e
{
    XU_STATE_OK            = XU_STATE_DEFINE(XU_STATE_TYPE_NONE, 0),
    XU_STATE_END           = XU_STATE_DEFINE(XU_STATE_TYPE_NONE, 1),
    XU_STATE_DEAD          = XU_STATE_DEFINE(XU_STATE_TYPE_NONE, 2),
    XU_STATE_READY         = XU_STATE_DEFINE(XU_STATE_TYPE_NONE, 3),
    XU_STATE_FAILED        = XU_STATE_DEFINE(XU_STATE_TYPE_NONE, 4),
    XU_STATE_KILLED        = XU_STATE_DEFINE(XU_STATE_TYPE_NONE, 5),
    XU_STATE_PAUSED        = XU_STATE_DEFINE(XU_STATE_TYPE_NONE, 6),
    XU_STATE_CLOSED        = XU_STATE_DEFINE(XU_STATE_TYPE_NONE, 7),
    XU_STATE_OPENED        = XU_STATE_DEFINE(XU_STATE_TYPE_NONE, 8),
    XU_STATE_OPENING       = XU_STATE_DEFINE(XU_STATE_TYPE_NONE, 9),
    XU_STATE_SUSPEND       = XU_STATE_DEFINE(XU_STATE_TYPE_NONE, 10),
    XU_STATE_RUNNING       = XU_STATE_DEFINE(XU_STATE_TYPE_NONE, 11),
    XU_STATE_PENDING       = XU_STATE_DEFINE(XU_STATE_TYPE_NONE, 12),
    XU_STATE_WAITING       = XU_STATE_DEFINE(XU_STATE_TYPE_NONE, 13),
    XU_STATE_WORKING       = XU_STATE_DEFINE(XU_STATE_TYPE_NONE, 14),
    XU_STATE_KILLING       = XU_STATE_DEFINE(XU_STATE_TYPE_NONE, 15),
    XU_STATE_PAUSING       = XU_STATE_DEFINE(XU_STATE_TYPE_NONE, 16),
    XU_STATE_EXITING       = XU_STATE_DEFINE(XU_STATE_TYPE_NONE, 17),
    XU_STATE_TIMEOUT       = XU_STATE_DEFINE(XU_STATE_TYPE_NONE, 18),
    XU_STATE_FINISHED      = XU_STATE_DEFINE(XU_STATE_TYPE_NONE, 19),
    XU_STATE_WAIT_FAILED   = XU_STATE_DEFINE(XU_STATE_TYPE_NONE, 20),
    XU_STATE_POST_FAILED   = XU_STATE_DEFINE(XU_STATE_TYPE_NONE, 21),
    XU_STATE_NOT_SUPPORTED = XU_STATE_DEFINE(XU_STATE_TYPE_NONE, 22),
    XU_STATE_UNKNOWN_ERROR = XU_STATE_DEFINE(XU_STATE_TYPE_NONE, 23)

        ,
    XU_STATE_SOCK_DNS_FAILED        = XU_STATE_DEFINE(XU_STATE_TYPE_SOCK, 1),
    XU_STATE_SOCK_CONNECT_FAILED    = XU_STATE_DEFINE(XU_STATE_TYPE_SOCK, 2),
    XU_STATE_SOCK_CONNECT_TIMEOUT   = XU_STATE_DEFINE(XU_STATE_TYPE_SOCK, 3),
    XU_STATE_SOCK_RECV_TIMEOUT      = XU_STATE_DEFINE(XU_STATE_TYPE_SOCK, 4),
    XU_STATE_SOCK_SEND_TIMEOUT      = XU_STATE_DEFINE(XU_STATE_TYPE_SOCK, 5),
    XU_STATE_SOCK_RECV_FAILED       = XU_STATE_DEFINE(XU_STATE_TYPE_SOCK, 6),
    XU_STATE_SOCK_SEND_FAILED       = XU_STATE_DEFINE(XU_STATE_TYPE_SOCK, 7),
    XU_STATE_SOCK_OPEN_FAILED       = XU_STATE_DEFINE(XU_STATE_TYPE_SOCK, 8),
    XU_STATE_SOCK_UNKNOWN_ERROR     = XU_STATE_DEFINE(XU_STATE_TYPE_SOCK, 9),
    XU_STATE_SOCK_SSL_FAILED        = XU_STATE_DEFINE(XU_STATE_TYPE_SOCK, 10),
    XU_STATE_SOCK_SSL_TIMEOUT       = XU_STATE_DEFINE(XU_STATE_TYPE_SOCK, 11),
    XU_STATE_SOCK_SSL_WANT_READ     = XU_STATE_DEFINE(XU_STATE_TYPE_SOCK, 12),
    XU_STATE_SOCK_SSL_WANT_WRIT     = XU_STATE_DEFINE(XU_STATE_TYPE_SOCK, 13),
    XU_STATE_SOCK_SSL_WAIT_FAILED   = XU_STATE_DEFINE(XU_STATE_TYPE_SOCK, 14),
    XU_STATE_SOCK_SSL_READ_FAILED   = XU_STATE_DEFINE(XU_STATE_TYPE_SOCK, 15),
    XU_STATE_SOCK_SSL_WRIT_FAILED   = XU_STATE_DEFINE(XU_STATE_TYPE_SOCK, 16),
    XU_STATE_SOCK_SSL_NOT_SUPPORTED = XU_STATE_DEFINE(XU_STATE_TYPE_SOCK, 17),
    XU_STATE_SOCK_SSL_UNKNOWN_ERROR = XU_STATE_DEFINE(XU_STATE_TYPE_SOCK, 18)

        ,
    XU_STATE_HTTP_RESPONSE_100       = XU_STATE_DEFINE(XU_STATE_TYPE_HTTP, 1),
    XU_STATE_HTTP_RESPONSE_101       = XU_STATE_DEFINE(XU_STATE_TYPE_HTTP, 2),
    XU_STATE_HTTP_RESPONSE_102       = XU_STATE_DEFINE(XU_STATE_TYPE_HTTP, 3),
    XU_STATE_HTTP_RESPONSE_200       = XU_STATE_DEFINE(XU_STATE_TYPE_HTTP, 4),
    XU_STATE_HTTP_RESPONSE_204       = XU_STATE_DEFINE(XU_STATE_TYPE_HTTP, 5),
    XU_STATE_HTTP_RESPONSE_300       = XU_STATE_DEFINE(XU_STATE_TYPE_HTTP, 6),
    XU_STATE_HTTP_RESPONSE_301       = XU_STATE_DEFINE(XU_STATE_TYPE_HTTP, 7),
    XU_STATE_HTTP_RESPONSE_302       = XU_STATE_DEFINE(XU_STATE_TYPE_HTTP, 8),
    XU_STATE_HTTP_RESPONSE_303       = XU_STATE_DEFINE(XU_STATE_TYPE_HTTP, 9),
    XU_STATE_HTTP_RESPONSE_304       = XU_STATE_DEFINE(XU_STATE_TYPE_HTTP, 10),
    XU_STATE_HTTP_RESPONSE_305       = XU_STATE_DEFINE(XU_STATE_TYPE_HTTP, 11),
    XU_STATE_HTTP_RESPONSE_306       = XU_STATE_DEFINE(XU_STATE_TYPE_HTTP, 12),
    XU_STATE_HTTP_RESPONSE_307       = XU_STATE_DEFINE(XU_STATE_TYPE_HTTP, 13),
    XU_STATE_HTTP_RESPONSE_400       = XU_STATE_DEFINE(XU_STATE_TYPE_HTTP, 14),
    XU_STATE_HTTP_RESPONSE_401       = XU_STATE_DEFINE(XU_STATE_TYPE_HTTP, 15),
    XU_STATE_HTTP_RESPONSE_402       = XU_STATE_DEFINE(XU_STATE_TYPE_HTTP, 16),
    XU_STATE_HTTP_RESPONSE_403       = XU_STATE_DEFINE(XU_STATE_TYPE_HTTP, 17),
    XU_STATE_HTTP_RESPONSE_404       = XU_STATE_DEFINE(XU_STATE_TYPE_HTTP, 18),
    XU_STATE_HTTP_RESPONSE_405       = XU_STATE_DEFINE(XU_STATE_TYPE_HTTP, 19),
    XU_STATE_HTTP_RESPONSE_406       = XU_STATE_DEFINE(XU_STATE_TYPE_HTTP, 20),
    XU_STATE_HTTP_RESPONSE_407       = XU_STATE_DEFINE(XU_STATE_TYPE_HTTP, 21),
    XU_STATE_HTTP_RESPONSE_408       = XU_STATE_DEFINE(XU_STATE_TYPE_HTTP, 22),
    XU_STATE_HTTP_RESPONSE_409       = XU_STATE_DEFINE(XU_STATE_TYPE_HTTP, 23),
    XU_STATE_HTTP_RESPONSE_410       = XU_STATE_DEFINE(XU_STATE_TYPE_HTTP, 24),
    XU_STATE_HTTP_RESPONSE_411       = XU_STATE_DEFINE(XU_STATE_TYPE_HTTP, 25),
    XU_STATE_HTTP_RESPONSE_412       = XU_STATE_DEFINE(XU_STATE_TYPE_HTTP, 26),
    XU_STATE_HTTP_RESPONSE_413       = XU_STATE_DEFINE(XU_STATE_TYPE_HTTP, 27),
    XU_STATE_HTTP_RESPONSE_414       = XU_STATE_DEFINE(XU_STATE_TYPE_HTTP, 28),
    XU_STATE_HTTP_RESPONSE_415       = XU_STATE_DEFINE(XU_STATE_TYPE_HTTP, 29),
    XU_STATE_HTTP_RESPONSE_416       = XU_STATE_DEFINE(XU_STATE_TYPE_HTTP, 30),
    XU_STATE_HTTP_RESPONSE_500       = XU_STATE_DEFINE(XU_STATE_TYPE_HTTP, 31),
    XU_STATE_HTTP_RESPONSE_501       = XU_STATE_DEFINE(XU_STATE_TYPE_HTTP, 32),
    XU_STATE_HTTP_RESPONSE_502       = XU_STATE_DEFINE(XU_STATE_TYPE_HTTP, 33),
    XU_STATE_HTTP_RESPONSE_503       = XU_STATE_DEFINE(XU_STATE_TYPE_HTTP, 34),
    XU_STATE_HTTP_RESPONSE_504       = XU_STATE_DEFINE(XU_STATE_TYPE_HTTP, 35),
    XU_STATE_HTTP_RESPONSE_505       = XU_STATE_DEFINE(XU_STATE_TYPE_HTTP, 36),
    XU_STATE_HTTP_RESPONSE_506       = XU_STATE_DEFINE(XU_STATE_TYPE_HTTP, 37),
    XU_STATE_HTTP_RESPONSE_507       = XU_STATE_DEFINE(XU_STATE_TYPE_HTTP, 38),
    XU_STATE_HTTP_RESPONSE_UNK       = XU_STATE_DEFINE(XU_STATE_TYPE_HTTP, 39),
    XU_STATE_HTTP_RESPONSE_NUL       = XU_STATE_DEFINE(XU_STATE_TYPE_HTTP, 40),
    XU_STATE_HTTP_REQUEST_FAILED     = XU_STATE_DEFINE(XU_STATE_TYPE_HTTP, 41),
    XU_STATE_HTTP_REDIRECT_FAILED    = XU_STATE_DEFINE(XU_STATE_TYPE_HTTP, 42),
    XU_STATE_HTTP_POST_FAILED        = XU_STATE_DEFINE(XU_STATE_TYPE_HTTP, 43),
    XU_STATE_HTTP_RANGE_INVALID      = XU_STATE_DEFINE(XU_STATE_TYPE_HTTP, 44),
    XU_STATE_HTTP_GZIP_NOT_SUPPORTED = XU_STATE_DEFINE(XU_STATE_TYPE_HTTP, 45),
    XU_STATE_HTTP_UNKNOWN_ERROR      = XU_STATE_DEFINE(XU_STATE_TYPE_HTTP, 46)

        ,
    XU_STATE_DATABASE_NO_SUCH_TABLE     = XU_STATE_DEFINE(XU_STATE_TYPE_DATABASE, 1),
    XU_STATE_DATABASE_NO_SUCH_FIELD     = XU_STATE_DEFINE(XU_STATE_TYPE_DATABASE, 2),
    XU_STATE_DATABASE_NO_SUCH_DATABASE  = XU_STATE_DEFINE(XU_STATE_TYPE_DATABASE, 3),
    XU_STATE_DATABASE_ACCESS_DENIED     = XU_STATE_DEFINE(XU_STATE_TYPE_DATABASE, 4),
    XU_STATE_DATABASE_PARSE_ERROR       = XU_STATE_DEFINE(XU_STATE_TYPE_DATABASE, 5),
    XU_STATE_DATABASE_VALUE_COUNT_ERROR = XU_STATE_DEFINE(XU_STATE_TYPE_DATABASE, 6),
    XU_STATE_DATABASE_UNKNOWN_HOST      = XU_STATE_DEFINE(XU_STATE_TYPE_DATABASE, 7),
    XU_STATE_DATABASE_UNKNOWN_ERROR     = XU_STATE_DEFINE(XU_STATE_TYPE_DATABASE, 8)

        ,
    XU_STATE_SYSERROR_NOT_PERM      = XU_STATE_DEFINE(XU_STATE_TYPE_SYSERROR, 1),
    XU_STATE_SYSERROR_NOT_FILEDIR   = XU_STATE_DEFINE(XU_STATE_TYPE_SYSERROR, 2),
    XU_STATE_SYSERROR_NOT_ACCESS    = XU_STATE_DEFINE(XU_STATE_TYPE_SYSERROR, 3),
    XU_STATE_SYSERROR_UNKNOWN_ERROR = XU_STATE_DEFINE(XU_STATE_TYPE_SYSERROR, 4)

} xu_state_e;

/* *******************************************************
 *  interfaces
 */

/*! the state string
 *
 * @param state     the state
 *
 * @return          the state string
 */
xu_char_t const* xu_state_cstr(xu_size_t state);
